<?php

namespace api\modules\v1\controllers\infusion;

use common\helpers\CommonHelper;
use common\helpers\RedisHelper;
use common\models\patient\InfusionQueue;
use services\infusion\QueueService;
use services\patient\DrugSurplusService;
use services\rbac\DepartmentService;
use Yii;
use api\controllers\OnAuthController;
use common\models\patient\User;

/**
 * 排队
 * Class QueueController
 * @package api\modules\v1\controllers\infusion
 */
class QueueController extends OnAuthController
{
    /**
     * @var User
     */
    public $modelClass = User::class;

    protected $optional = [];
    protected $optionalLimit = [];

    /**
     * @api {get} /v1/infusion/queue/list 排队列表
     * @apiName list
     * @apiGroup InfusionQueue
     *
     * @apiParam {Number} type                              类型【0全部、1静滴、2肌注】
     *
     * @apiSuccess {Array}  data                            返回内容
     * @apiSuccess {Array}  data.jd                         静滴队列
     * @apiSuccess {Array}  data.jz                         肌注队列
     * @apiSuccess {Number} data.wait_time                  等待时间
     *
     */
    public function actionList()
    {
        $params = Yii::$app->request->get();
        $type = $params['type'] ?? 0;

        $service = new QueueService();
        // 查询结果
        $data = $service->getQueueList($params, (int)$type);

        return $data;
    }

    /**
     * @api {get} /v1/infusion/queue/info 排队信息
     * @apiName info
     * @apiGroup InfusionQueue
     *
     * @apiParam {Number} id                                排队ID
     *
     * @apiSuccess {Array}  data                            返回内容
     *
     */
    public function actionInfo()
    {
        $params = Yii::$app->request->get();
        $id = $params['id'] ?? 0;

        $service = new QueueService();
        // 队列信息
        $data = $service->getQueueInfo((int)$id);
        // 操作人员
        $dService = new DepartmentService();
        $data['operate_member_list'] = $dService->getInfusionDepartmentUserList();

        return $data;
    }

    /**
     * @api {get} /v1/infusion/queue/patient-drug-list      患者药品列表
     * @apiName patient-drug-list
     * @apiGroup InfusionQueue
     *
     * @apiParam {Number} id                                患者ID
     *
     * @apiSuccess {Array}  data                            返回内容
     * @apiSuccess {Array}  data.jd                         静滴药品
     * @apiSuccess {Array}  data.jz                         肌注药品
     *
     */
    public function actionPatientDrugList()
    {
        $params = Yii::$app->request->get();
        $id = $params['id'] ?? 0;

        $service = new DrugSurplusService();
        // 查询结果
        $data = $service->getPatientDrugList((int)$id);

        $queueService = new QueueService();
        $queueData = $queueService->getPatientWaitingInfo($id);

        return array_merge($data, $queueData);
    }

    /**
     * @api {post} /v1/infusion/queue/create                 排队
     * @apiName create
     * @apiGroup InfusionQueue
     *
     * @apiParam {Number} patient_user_id                   患者ID
     * @apiParam {String} surplus_drug_id                   患者剩余药品ID【多个用’,‘分割】
     * @apiParam {Number} type                              排队类型【1静滴、2肌注】
     *
     * @apiSuccess {Array}  data                            返回内容
     * @apiSuccess {Number} data.id                         ID
     *
     */
    public function actionCreate()
    {
        try {
            $params = Yii::$app->request->post();
            $type = intval($params['type'] ?? 0);

            // lock
            $key = "hcrm:infusion:queue:{$this->projectId}_{$type}";
            $lock = RedisHelper::lock($key, 30);
            if (!$lock) {
                throw new \Exception('系统拥堵，请重新排队');
            }
            // 事务开启
            $transaction = Yii::$app->db->beginTransaction();

            $service = new QueueService();
            $data = $service->create($params);

            $transaction->commit();
            RedisHelper::unlock($key);// 正常，解锁

            // 通知websocket白友+大屏排队成功
            CommonHelper::rpcRequest('Queue', 'QueueModule', 'create', ['project_id' => Yii::$app->params['project_id']]);

        } catch (\Exception $e) {
            isset($transaction) && $transaction->rollBack();
            RedisHelper::unlock($key);// 失败，解锁
            $data = CommonHelper::api(422, $e->getMessage());
        }

        return $data;
    }

    /**
     * @api {post} /v1/infusion/queue/call                  叫号
     * @apiName call
     * @apiGroup InfusionQueue
     *
     * @apiParam {Number} id                                队列ID
     *
     * @apiSuccess {Array}  data                            返回内容
     * @apiSuccess {Number} data.id                         ID
     *
     */
    public function actionCall()
    {
        try {
            $params = Yii::$app->request->post();
            // 类型
            $id = intval($params['id'] ?? 0);
            $queue = InfusionQueue::findOne($id);
            $type = $queue ? $queue->type : 0;

            // lock
            $key = "hcrm:infusion:call:{$this->projectId}_{$type}";
            $lock = RedisHelper::lock($key, InfusionQueue::WAIT_TIME, 2);
            if ($lock) {
                $service = new QueueService();
                $data = $service->call($params);

                if (!isset($data['code'])) {
                    // 通知websocket大屏叫号成功
                    CommonHelper::rpcRequest('Queue', 'QueueModule', 'call', ['project_id' => Yii::$app->params['project_id'], 'id' => $data['id'] ?? 0]);
                }
            } else {
                $data = CommonHelper::api(422, "存在叫号患者，请耐心等待");
            }
        } catch (\Exception $e) {
            isset($lock) && $lock && RedisHelper::unlock($key);// 失败，解锁
            $data = CommonHelper::api(422, $e->getMessage());
        }

        return $data;
    }

    /**
     * @api {post} /v1/infusion/queue/infusion              输液
     * @apiName infusion
     * @apiGroup InfusionQueue
     *
     * @apiParam {Number} id                                队列ID
     * @apiParam {Number} operate_id                        操作人ID
     *
     * @apiSuccess {Array}  data                            返回内容
     * @apiSuccess {Number} data.id                         ID
     *
     */
    public function actionInfusion()
    {
        try {
            // 事务开启
            $transaction = Yii::$app->db->beginTransaction();

            $params = Yii::$app->request->post();
            $params['id'] = $params['id'] ?? 0;
            // lock
            $key = "hcrm:infusion:shuye_queue:{$params['id']}";
            $lock = RedisHelper::lock($key, 5);
            if (!$lock) {
                throw new \Exception('正在请求当中，请勿重复操作');
            }

            $service = new QueueService();
            $data = $service->infusion($params);

            $transaction->commit();
            RedisHelper::unlock($key);// 正常，解锁
            // 通知websocket大屏叫号成功
            if (isset($data['id'])) {
                CommonHelper::rpcRequest('Queue', 'QueueModule', 'infusion', ['project_id' => Yii::$app->params['project_id'], 'id' => $data['id'] ?? 0, 'type' => $data['type']]);
            }
        } catch (\Exception $e) {
            $transaction->rollBack();
            RedisHelper::unlock($key);// 正常，解锁
            $data = CommonHelper::api(422, $e->getMessage());
        }

        return $data;
    }

    /**
     * @api {post} /v1/infusion/queue/cancel                撤销
     * @apiName cancel
     * @apiGroup InfusionQueue
     *
     * @apiParam {Number} id                                队列ID
     *
     * @apiSuccess {Array}  data                            返回内容
     * @apiSuccess {Number} data.id                         ID
     *
     */
    public function actionCancel()
    {
        try {
            $params = Yii::$app->request->post();

            $service = new QueueService();
            $data = $service->cancel($params);

            // 通知websocket大屏叫号成功
            if (isset($data['id'])) {
                CommonHelper::rpcRequest('Queue', 'QueueModule', 'cancel', ['project_id' => Yii::$app->params['project_id']]);
            }
        } catch (\Exception $e) {
            $data = CommonHelper::api(422, $e->getMessage());
        }

        return $data;
    }

    /**
     * @api {get} /v1/infusion/queue/check-treatment-today 检测患者当天是否做过治疗
     * @apiName check-treatment-today
     * @apiGroup InfusionQueue
     *
     * @apiParam {Number} patient_user_id                             患者ID
     * @apiParam {Number} drug_config_id                              药品配置ID
     *
     * @apiSuccess {Array}  data                            返回内容
     *
     */
    public function actionCheckTreatmentToday()
    {
        $params = Yii::$app->request->get();
        $params['patient_user_id'] = $params['patient_user_id'] ?? 0;
        $params['drug_config_id'] = $params['drug_config_id'] ?? 0;
        $service = new DrugSurplusService();
        return $service->checkTreatmentToday($params);
    }
}
